// Include standard headers
#include <fstream>
#include <iostream>
#include <math.h>
#include <string.h>

using namespace std;

// Include GLM
#include <glm/glm.hpp>

using namespace glm;

#ifndef ANIMATION_HPP
#define ANIMATION_HPP

#define uint unsigned int

#define MAX_CHSIZE                  12
#define BONE_ABSOLUTE_ANGLE         0x01	/* Bone angle is absolute or relative to parent */
#define BONE_ABSOLUTE_POSITION      0x02	/* Bone position is absolute in the world or relative to the parent */
#define BONE_ABSOLUTE               (BONE_ABSOLUTE_ANGLE | BONE_ABSOLUTE_POSITION)

class JOINT{
public:
    char *name;
    int num;

    //Offset
    vec3 offset;

    //Chanel table
    vec3 *channel;

    JOINT *parent;

    JOINT **childs;
    uint childsSize;

    virtual JOINT *addJOINT(JOINT *child);
    virtual void dumpTree(uint level);
    virtual void setChannel(vec3 **channelsTab, int *n);

    JOINT();

    JOINT(char *_name,
          uint _num,
          vec3 _offset,
          JOINT *_parent);
};

class ROOT : public JOINT{
public:
    //Position table
    vec3 *position;

    void setChannel(vec3 **channelsTab, int *n);

    ROOT(char *_name,
         vec3 _offset);
};

class ENDSITE : public JOINT{
public:

    void dumpTree(uint level);
    void setChannel(vec3 **channelsTab, int *n);

    ENDSITE(uint _num, vec3 _offset, JOINT *_parent);
};

class BVH{
public:
    ROOT *root;

    uint bonesNum;

    uint frames;
    float frameTime;

    int loadHIERARCHY(FILE *file);
    bool loadMOTION(FILE *file, int channels, uint frames);
    BVH(char *filepath);

    void dumpTree();
};
#endif
